-- A lot of these codes are from Nova Team, Major thanks to them and Credits as well.
-- Sheuron Healing engine is used as well as some other function he wrote, Thanks to the
-- devs that worked hard to make this up.


if not PQR_LoadedDataFile then
	PQR_LoadedDateFile = 1
	print("|cffFFBE69Rekrouk Data Sheet |cffffffffv 1.08 |cffFFBE69loaded succesfully.")
end

--------------------------------------------------------------------------------------------------
--									Nova Functions												--
--------------------------------------------------------------------------------------------------
Nova_UnitInfo = nil
function Nova_UnitInfo(t)
	-- Takes an input of UnitID (player, target, pet, mouseover, etc) and gives you their most useful info
		local TManaActual = UnitPower(t)
		local TMaxMana = UnitPowerMax(t)
		if TMaxMana == 0 then TMaxMana = 1 end			
		local TMana = 100 * UnitPower(t) / TMaxMana
		local THealthActual = UnitHealth(t)
		local THealth = 100 * UnitHealth(t) / UnitHealthMax(t) 
		local myClassPower = 0 
		local PQ_Class = select(2, UnitClass(t)) 
		local PQ_UnitLevel = UnitLevel(t)
		local PQ_CombatCheck = UnitAffectingCombat(t) 
		if PQ_Class == "PALADIN" then
			myClassPower = UnitPower("player", 9)
			if UnitBuffID("player", 90174) then
				myClassPower = myClassPower + 3
			end
		elseif PQ_Class == "PRIEST" then
			myClassPower = UnitPower("player", 13)
		elseif PQ_Class == "WARLOCK" then
			if PQR_Spec == 3 then
				myClassPower = UnitPower("player", 14) -- Destruction: Burning Embers
			elseif PQR_Spec == 2 then
				myClassPower = UnitPower("player", 15) -- Demonology: Demonic Fury
			elseif PQR_Spec == 1 then
				myClassPower = UnitPower("player", 7) -- Affliction: Soul Shards
			end
		elseif PQ_Class == "DRUID" and PQ_Class == 2 then
			myClassPower = UnitPower("player", 8)
		elseif PQ_Class == "MONK"  then
			myClassPower = UnitPower("player", 12)
		elseif PQ_Class == "ROGUE" and t ~= "player" then
			myClassPower = GetComboPoints("player", t)
		end
		--       1            2          3         4           5             6          7               8
		return THealth, THealthActual, TMana, TManaActual, myClassPower, PQ_Class, PQ_UnitLevel, PQ_CombatCheck
end

-- Self Explainatory
GlyphCheck = nil
function GlyphCheck(glyphid)
	for i=1, 6 do
		if select(4, GetGlyphSocketInfo(i)) == glyphid then
			return true
		end
	end
	return false
end

Nova_TargetInfo = nil
function Nova_TargetInfo(t)
	local TManaActual = UnitPower(t)
		local TMana = 100 
		local THealthActual = UnitHealth(t)
	local THealth = 100 * UnitHealth(t) / UnitHealthMax(t) 
	return THealth, THealthActual, TMana, TManaActual
end

--Tabled Cast Time Checking for When you Last Cast Something.
CheckCastTime = {}
Nova_CheckLastCast = nil
function Nova_CheckLastCast(spellid, ytime) -- SpellID of Spell To Check, How long of a gap are you looking for?
	if ytime > 0 then
		if #CheckCastTime > 0 then
			for i=1, #CheckCastTime do
				if CheckCastTime[i].SpellID == spellid then
					if GetTime() - CheckCastTime[i].CastTime > ytime then
						CheckCastTime[i].CastTime = GetTime()
						return true
					else
						return false
					end
				end
			end
		end
		table.insert(CheckCastTime, { SpellID = spellid, CastTime = GetTime() } )
		return true
	elseif ytime <= 0 then
		return true
	end
	return false
end

-- This is used for Shorter Threat Check Situations and PvP
Nova_ThreatCheck = nil
function Nova_ThreatCheck(unit1, unit2)
	if UnitIsPlayer(unit1) and UnitIsPlayer(unit2) then
		if UnitIsUnit(unit1, unit2.."target") then
			return true
		end
	elseif UnitDetailedThreatSituation(unit1, unit2) then
		return true
	end
	return false
end

-- Simplifying Range Check
Nova_Range = nil
function Nova_Range(spellid, spelltarget)
	if GetSpellInfo(spellid)
	 and UnitExists(spelltarget) then
	 	if IsSpellInRange(GetSpellInfo(spellid), spelltarget) == 1 then
	 		return true
	 	elseif IsSpellInRange(GetSpellInfo(spellid), spelltarget) == 0 then
	 		return false
	 	else
	 		return false
	 	end
	end
end

-- GUID Finder
Nova_GUID = nil
function Nova_GUID(unit)
	if UnitExists(unit) then
		if UnitIsPlayer(unit) then
			targetGUID = UnitGUID(unit)
		else
			targetGUID = tonumber((UnitGUID(unit)):sub(-12, -9), 16)
		end
	end
		
	return targetGUID
end

Nova_CastingInfo = nil
function Nova_CastingInfo(PQ_Unit)
	local PQ_Casting = nil
	local percentRemaining = nil
	local secondsRemaining = nil

	if UnitCastingInfo(PQ_Unit) then
		local spellName,_,_,_,startTimer,endTimer = UnitCastingInfo(PQ_Unit)
		local durationTimer = ((endTimer) - (startTimer))
		local timeRemaining = (endTimer - GetTime() * 1000)
		percentRemaining = (100 - ((timeRemaining/durationTimer) * 100))
		secondsRemaining = endTimer/1000 - GetTime()
		PQ_Casting = spellName
		
		-- Name of spell, % remaining on spell, seconds remaining on spell
		return PQ_Casting, percentRemaining, secondsRemaining
	else return false end
end

-- Target Validation Function.
TargetValidation = nil
function TargetValidation(unit, spell)
	if UnitExists(unit)
	 and IsPlayerSpell(spell)
	 and UnitCanAttack("player", unit) == 1 
	 and PQR_UnitFacing("player", unit)
	 and not UnitIsDeadOrGhost(unit) 
	 and not PQR_IsOutOfSight(unit, 1) then
	 	if IsSpellKnown(spell) then  -- Redundent Check to see if Morphed Spell or not
	 		if PQR_SpellAvailable(spell) then
		 		if IsSpellInRange(GetSpellInfo(spell), unit) == 1 then
		 			return true
		 		else
		 			return false
		 		end
		 	else
		 		return false
		 	end
	 	else -- If spell is a morphed spell, return true without Range Check
	 		if select(2, GetSpellCooldown(spell)) <= 2 then
	 			return true
	 		end
	 	end
	end
end

-- Killing Raid/Party members with dots are bad
isMindControledUnit = nil
function isMindControledUnit(unit)
	-- Determine our Group setting.
	if IsInRaid() then group = "raid"
		elseif IsInGroup() then group = "party"
	else return true end
		
	-- Stop dots.
	for i=1,GetNumGroupMembers() do
		local member = group..i
		if not UnitCanAttack("player",unit) then return true
		else
			if UnitName(unit) == member then return false end
		end
		return true
	end
end

---------------------------------
-- Debug & Notification Frame
---------------------------------
-- Update Debug Frame
Nova_NotifyFrame = nil
function Nova_NotifyFrame_OnUpdate()
	if (Nova_NotifyFrameTime < GetTime() - 0.2) then
		local alpha = Nova_NotifyFrame:GetAlpha()
		if (alpha ~= 0) then Nova_NotifyFrame:SetAlpha(alpha - .5) end
		if (aplha == 0) then Nova_NotifyFrame:Hide() end
	end
end

-- Debug messages.
function Nova_Notify(message)
	Nova_NotifyFrame.text:SetText(message)
	Nova_NotifyFrame:SetAlpha(1)
	Nova_NotifyFrame:Show()
	Nova_NotifyFrameTime = GetTime()
end

-- Debug Notification Frame
Nova_NotifyFrame = CreateFrame('Frame')
Nova_NotifyFrame:ClearAllPoints()
Nova_NotifyFrame:SetHeight(300)
Nova_NotifyFrame:SetWidth(300)
Nova_NotifyFrame:SetScript('OnUpdate', Nova_NotifyFrame_OnUpdate)
Nova_NotifyFrame:Hide()
Nova_NotifyFrame.text = Nova_NotifyFrame:CreateFontString(nil, 'BACKGROUND', 'PVPInfoTextFont')
Nova_NotifyFrame.text:SetAllPoints()
Nova_NotifyFrame:SetPoint('LEFT', 40, - 75)
Nova_NotifyFrameTime = 0

--------------------------------------------------------------------------------------------------
--									Copied Functions											--
--------------------------------------------------------------------------------------------------
Nova_CustomT = { }

----------------------------------------------
-- Sheuron Healing Functions
----------------------------------------------
function CalculateHP(t)
	incomingheals = UnitGetIncomingHeals(t) and UnitGetIncomingHeals(t) or 0
	local PercentWithIncoming = 100 * ( UnitHealth(t) + incomingheals ) / UnitHealthMax(t)
	local ActualWithIncoming = ( UnitHealthMax(t) - ( UnitHealth(t) + incomingheals ) )
	return PercentWithIncoming, ActualWithIncoming
end

function CanHeal(t)
	if UnitInRange(t) 
		and UnitCanCooperate("player",t) 
		and not UnitIsCharmed(t) 
		and not UnitIsDeadOrGhost(t) 
		and not PQR_IsOutOfSight(t) 
		and UnitIsConnected(t)
		and UnitDebuffID(t,104451) == nil -- Ice Tomb
		and UnitDebuffID(t,76577) == nil -- Smoke Bomb
		and UnitDebuffID(t, 121949) == nil -- Parasistic Growth
		and UnitDebuffID(t, 122784) == nil -- Reshape Life
		and UnitDebuffID(t, 122370) == nil -- Reshape Life 2
		and UnitDebuffID(t, 123184) == nil -- Dissonance Field
		and UnitDebuffID(t, 123255) == nli -- Dissonance Field 2
		and UnitDebuffID(t, 123596) == nil -- Dissonance Field 3 
		and UnitDebuffID(t, 128353) == nil -- Dissonance Field 4
		then return true else return false end 
end

function SheuronEngine(MO, LOWHP, ACTUALHP)
	Nova_Tanks = { }
	local MouseoverCheck = MO or false
	local ActualHP = ACTUALHP or false
	local LowHPTarget = LOWHP or 65
	lowhpmembers = 0
	members = { { Unit = "player", HP = CalculateHP("player"), GUID = UnitGUID("player"), AHP = select(2, CalculateHP("player")) } } 
	
	-- Check if the Player is apart of the Custom Table
	for i=1, #Nova_CustomT do 
		if UnitGUID("player") == Nova_CustomT[i].GUID then 
			Nova_CustomT[i].Unit = "player" 
			Nova_CustomT[i].HP = CalculateHP("player")
			Nova_CustomT[i].AHP = select(2, CalculateHP("player")) 
		end 
	end

	if IsInRaid() then
			group = "raid"
	elseif IsInGroup() then
			group = "party"
	end
	
	for i = 1, GetNumGroupMembers() do 
		local member, memberhp = group..i, CalculateHP(group..i)
		
		-- Checking all Party/Raid Members for Range/Health
		if CanHeal(member) then 
			-- Checking if Member has threat
			if UnitThreatSituation(member) == 3 then memberhp = memberhp - 1 end
			-- Checking if Member has Beacon on them
			if UnitBuffID(member, 53563) then memberhp = memberhp + 3 end 
			-- Searing Plasma Check
			if UnitDebuffID(member, 109379) then memberhp = memberhp - 9 end
			-- Checking if Member is a tank
			if UnitGroupRolesAssigned(member) == "TANK" then 
				memberhp = memberhp - 1 
				table.insert(Nova_Tanks, { Unit = member, HP = memberhp, AHP = select(2, CalculateHP(member)) } )
			end			
			-- If they are in the Custom Table add their info in
			for i=1, #Nova_CustomT do 
				if UnitGUID(member) == Nova_CustomT[i].GUID then 
					Nova_CustomT[i].Unit = member 
					Nova_CustomT[i].HP = memberhp 
					Nova_CustomT[i].AHP = select(2, CalculateHP(member))
				end 
			end 
			
			table.insert( members,{ Unit = group..i, HP = memberhp, GUID = UnitGUID(group..i), AHP = select(2, CalculateHP(group..i)) } ) 
		end 
		
		-- Checking Pets in the group
		if CanHeal(group..i.."pet") then
			local memberpet, memberpethp = nil, nil
			if UnitAffectingCombat("player") then
				 memberpet = group..i.."pet" 
				 memberpethp = CalculateHP(group..i.."pet") * 2
			else
				 memberpet = group..i.."pet"
				 memberpethp = CalculateHP(group..i.."pet")
			end
			
			-- Checking if Pet is apart of the CustomTable
			for i=1, #Nova_CustomT do 
				if UnitGUID(memberpet) == Nova_CustomT[i].GUID then 
					Nova_CustomT[i].Unit = memberpet 
					Nova_CustomT[i].HP = memberpethp
					Nova_CustomT[i].AHP = select(2, CalculateHP(memberpet)) 
				end
			end
			
			table.insert(members, { Unit = memberpet, HP = memberpethp, GUID = UnitGUID(memberpet), AHP = select(2, CalculateHP(memberpet)) } )
		end
	end 
	
	-- So if we pass that ActualHP is true, then we will sort by most health missing. If not, we sort by lowest % of health.
	if not ActualHP then
		table.sort(members, function(x,y) return x.HP < y.HP end)
		if #Nova_Tanks > 0 then
			table.sort(Nova_Tanks, function(x,y) return x.HP < y.HP end)
		end
	elseif ActualHP then
		table.sort(members, function(x,y) return x.AHP > y.AHP end)
		if #Nova_Tanks > 0 then
			table.sort(Nova_Tanks, function(x,y) return x.AHP > y.AHP end)
		end
	end
	
	-- Setting Low HP Members variable for AoE Healing
	for i=1,#members do
		if members[i].HP < LowHPTarget then
			lowhpmembers = lowhpmembers + 1
		end
	end
	
	-- Checking Priority Targeting
	if CanHeal("target") then
		table.sort(members, function(x) return UnitIsUnit("target",x.Unit) end)
	elseif CanHeal("mouseover") and GetMouseFocus() ~= WorldFrame and MouseoverCheck then
		table.sort(members, function(x) return UnitIsUnit("mouseover",x.Unit) end)
	end
end

function CheckDistance(unit1,unit2)
	local x1,y1 = GetPlayerMapPosition(unit1)
	local x2,y2 = GetPlayerMapPosition(unit2)
	
	return sqrt( (x1-x2)^2 + (y1-y2)^2 )
end

function UnitsClose(t, percent)
	local PercentToHeal = percent or 85
	local n = 0
	
	if distance and distance[1] then
		for i=1,#members do
			local x = CheckDistance(t,members[i].Unit)
			if x ~= 0 and x < distance[1] and members[i].HP < PercentToHeal then n = n + 1 end
		end
	end
	return n
end

function GetDistance() 
	local playerx,playery = GetPlayerMapPosition("player")
	
	if GetCurrentMapAreaID() ~= xrnMap or GetCurrentMapDungeonLevel() ~= xrnDung then
		xrnMap,xrnDung = GetCurrentMapAreaID(), GetCurrentMapDungeonLevel()
		mp, distance = {}, {}
	end
	
	if #members > 1 and #distance < 10 and playerx ~= 0 and playery ~= 0 then
		for i=1,#members do
			if CheckInteractDistance(members[i].Unit,2) then
				mp[members[i].Unit] = {GetPlayerMapPosition(members[i].Unit)}
			elseif UnitInRange(members[i].Unit) and mp[members[i].Unit] then
				table.insert(distance,sqrt((mp[members[i].Unit][1] - playerx)^2 + (mp[members[i].Unit][2] - playery)^2))
				table.sort(distance)
				mp[members[i].Unit] = nil
			end
		end
	end
end

function CastClick()

	if IsMouseButtonDown(1) 
	  and MainMenuBar:IsShown() then
	  
		local mousefocus = GetMouseFocus()
		
		if mousefocus 
		  and mousefocus.feedback_action then 
		  
		  	SpellCancelQueuedSpell() 
		  	PQR_DelayRotation(1) 
		  	
		end
	end 
end
--------------------------------------------------------------------------------------------------
--									Libraries													--
--------------------------------------------------------------------------------------------------
-------------------------------------------------------------------------------
-- Target & Environmental Globals and Tables
-------------------------------------------------------------------------------
PQ_Shrapnel			= {106794,106791}
PQ_FadingLight		= {105925,105926,109075,109200}
PQ_HourOfTwilight	= {106371,103327,106389,106174,106370}


-- Heroism Function.
PQ_HasHero = nil
function PQ_HasHero()
	local PQ_BL = PQ_BloodLust
	local PQ_Hero = PQ_Heroism
	local PQ_TW = PQ_TimeWarp
	local PQ_AH = PQ_Hysteria

	if UnitBuffID("player",PQ_BL)
		or UnitBuffID("player",PQ_Hero)
		or UnitBuffID("player",PQ_TW)
		or UnitBuffID("player",PQ_AH)
	then return true else return false end
end

PQ_BossUnits = {
	-- Cataclysm Dungeons --
	-- Abyssal Maw: Throne of the Tides
	40586,		-- Lady Naz'jar
	40765,		-- Commander Ulthok
	40825,		-- Erunak Stonespeaker
	40788,		-- Mindbender Ghur'sha
	42172,		-- Ozumat
	-- Blackrock Caverns
	39665,		-- Rom'ogg Bonecrusher
	39679,		-- Corla, Herald of Twilight
	39698,		-- Karsh Steelbender
	39700,		-- Beauty
	39705,		-- Ascendant Lord Obsidius
	-- The Stonecore
	43438,		-- Corborus
	43214,		-- Slabhide
	42188,		-- Ozruk
	42333,		-- High Priestess Azil
	-- The Vortex Pinnacle
	43878,		-- Grand Vizier Ertan
	43873,		-- Altairus
	43875,		-- Asaad
	-- Grim Batol
	39625,		-- General Umbriss
	40177,		-- Forgemaster Throngus
	40319,		-- Drahga Shadowburner
	40484,		-- Erudax
	-- Halls of Origination
	39425,		-- Temple Guardian Anhuur
	39428,		-- Earthrager Ptah
	39788,		-- Anraphet
	39587,		-- Isiset
	39731,		-- Ammunae
	39732,		-- Setesh
	39378,		-- Rajh
	-- Lost City of the Tol'vir
	44577,		-- General Husam
	43612,		-- High Prophet Barim
	43614,		-- Lockmaw
	49045,		-- Augh
	44819,		-- Siamat
	-- Zul'Aman
	23574,		-- Akil'zon
	23576,		-- Nalorakk
	23578,		-- Jan'alai
	23577,		-- Halazzi
	24239,		-- Hex Lord Malacrass
	23863,		-- Daakara
	-- Zul'Gurub
	52155,		-- High Priest Venoxis
	52151,		-- Bloodlord Mandokir
	52271,		-- Edge of Madness
	52059,		-- High Priestess Kilnara
	52053,		-- Zanzil
	52148,		-- Jin'do the Godbreaker
	-- End Time
	54431,		-- Echo of Baine
	54445,		-- Echo of Jaina
	54123,		-- Echo of Sylvanas
	54544,		-- Echo of Tyrande
	54432,		-- Murozond
	-- Hour of Twilight
	54590,		-- Arcurion
	54968,		-- Asira Dawnslayer
	54938,		-- Archbishop Benedictus
	-- Well of Eternity
	55085,		-- Peroth'arn
	54853,		-- Queen Azshara
	54969,		-- Mannoroth
	55419,		-- Captain Varo'then
	
	-- Mists of Pandaria Dungeons --
	-- Scarlet Halls
	59303,		-- Houndmaster Braun
	58632,		-- Armsmaster Harlan
	59150,		-- Flameweaver Koegler
	-- Scarlet Monastery
	59789,		-- Thalnos the Soulrender
	59223,		-- Brother Korloff
	3977,		-- High Inquisitor Whitemane
	60040,		-- Commander Durand
	-- Scholomance
	58633,		-- Instructor Chillheart
	59184,		-- Jandice Barov
	59153,		-- Rattlegore
	58722,		-- Lilian Voss
	58791,		-- Lilian's Soul
	59080,		-- Darkmaster Gandling
	-- Stormstout Brewery
	56637,		-- Ook-Ook
	56717,		-- Hoptallus
	59479,		-- Yan-Zhu the Uncasked
	-- Tempe of the Jade Serpent
	56448,		-- Wise Mari
	56843,		-- Lorewalker Stonestep
	59051,		-- Strife
	59726,		-- Peril
	58826,		-- Zao Sunseeker
	56732,		-- Liu Flameheart
	56762,		-- Yu'lon
	56439,		-- Sha of Doubt
	-- Mogu'shan Palace
	61444,		-- Ming the Cunning
	61442,		-- Kuai the Brute
	61445,		-- Haiyan the Unstoppable
	61243,		-- Gekkan
	61398,		-- Xin the Weaponmaster
	-- Shado-Pan Monastery
	56747,		-- Gu Cloudstrike
	56541,		-- Master Snowdrift
	56719,		-- Sha of Violence
	56884,		-- Taran Zhu
	-- Gate of the Setting Sun
	56906,		-- Saboteur Kip'tilak
	56589,		-- Striker Ga'dok
	56636,		-- Commander Ri'mok
	56877,		-- Raigonn
	-- Siege of Niuzao Temple
	61567,		-- Vizier Jin'bak
	61634,		-- Commander Vo'jak
	61485,		-- General Pa'valak
	62205,		-- Wing Leader Ner'onok

	-- Training Dummies --
	46647,		-- Level 85 Training Dummy
	67127,		-- Level 90 Training Dummy
	
	-- Pandaria Raid Adds --
	63346,		-- Tsulong: The Dark of Night
	62969,		-- Tsulong: Embodied Terror
	62977,		-- Tsulong: Frightspawn
	62919,		-- Tsulong: Unstable Sha
	61034,		-- Sha of Fear: Terror Spawn
	61003		-- Sha of Fear: Dread Spawn
}

SpecialUnit = nil
function SpecialUnit()
	local PQ_BossUnits = PQ_BossUnits
	
	if UnitExists("target") then
		local npcID = tonumber(UnitGUID("target"):sub(6,10), 16)
		
		-- Dungeons & Raids
		if UnitLevel("target") == -1 then return true else
			for i=1,#PQ_BossUnits do
				if PQ_BossUnits[i] == npcID then return true end
			end
			return false
		end
	else return false end
end


-- Special Aggro Conditions
PQ_Aggro = {
	60410, 	-- Elegon
	63053	-- Garalon's Leg
}

-------------------------------------------------------------------------------
-- Buff Globals
-------------------------------------------------------------------------------
-- Aura Info function.
buffs = {
	stat 		=	{ 90363, 20217,	115921, 1126 },
	stamina		= 	{ 469, 6307, 103127, 90364, 21562},
	atkpwr		= 	{ 19506, 57330,	6673 },
	atkspeed	=	{ 55610, 113742, 30809, 128432, 128433 },
	spllpwr		=	{ 77747, 109773, 126309, 61316, 1459 },
	spllhaste	= 	{ 24907, 15473, 51470, 49868 },
	crit		=	{ 17007, 1459, 61316, 116781, 97229, 24604, 90309, 126373, 126309 },
	mastery		=	{ 116956, 19740, 93435, 128997 },
}

PQ_AuraInfo = nil
function PQ_AuraInfo(i,unit)
	if i == 1 then
		for x = 1, #buffs.stat do
			local name, _, texture = UnitBuff(unit, (GetSpellInfo(buffs.stat[x])))
			if texture then
				return name, _, texture
			end
		end
	elseif i == 2 then
		for x = 1, #buffs.stamina do
			local name, _, texture = UnitBuff(unit, (GetSpellInfo(buffs.stamina[x])))
			if texture then
				return name, _, texture
			end
		end
	elseif i == 3 then
		for x = 1, #buffs.atkpwr do
			local name, _, texture = UnitBuff(unit, (GetSpellInfo(buffs.atkpwr[x])))
			if texture then
				return name, _, texture
			end
		end
	elseif i == 4 then
		for x = 1, #buffs.atkspeed do
			local name, _, texture = UnitBuff(unit, (GetSpellInfo(buffs.atkspeed[x])))
			if texture then
				return name, _, texture
			end
		end
	elseif i == 5 then
		for x = 1, #buffs.spllpwr do
			local name, _, texture = UnitBuff(unit, (GetSpellInfo(buffs.spllpwr[x])))
			if texture then
				return name, _, texture
			end
		end
	elseif i == 6 then
		for x = 1, #buffs.spllhaste do
			local name, _, texture = UnitBuff(unit, (GetSpellInfo(buffs.spllhaste[x])))
			if texture then
				return name, _, texture
			end
		end
	elseif i == 7 then
		for x = 1, #buffs.crit do
			local name, _, texture = UnitBuff(unit, (GetSpellInfo(buffs.crit[x])))
			if texture then
				return name, _, texture
			end
		end
	elseif i == 8 then
		for x = 1, #buffs.mastery do
			local name, _, texture = UnitBuff(unit, (GetSpellInfo(buffs.mastery[x])))
			if texture then
				return name, _, texture
			end
		end
	else 
		return nil, nil, nil
	end
end

-- Temporary Buffs
PQ_Lightweave		= 125487
PQ_PowerTorrent		= 74241
PQ_VolcanicPotion	= 79476
PQ_SynapseSprings	= 96230
PQ_JadeSerpent		= 105702
PQ_JadeSpirit		= 104993
PQ_BloodLust		= 2825
PQ_Heroism			= 32182
PQ_TimeWarp			= 80353
PQ_Hysteria			= 90355
PQ_Zerk				= 26297

-- Trinket Proc list
--buffList = {104423,128985,125487,96230,105702,104993,26297,33702,126577,2825,32182,80353,90355,126659,126478,136082,126605,126476,136089,138898,139133,138786,138703,138963}
buffList = {104423,128985,125487,96230,105702,104993,26297,33702,126577,2825,32182,80353,90355,126659,126478,136082,126605,126476,136089}

-- Temporary Bloodlust
Nova_Lust = {PQ_Bloodlust,PQ_Heroism,PQ_TimeWarp,PQ_Hysteria}

-- Temporary Buff Table
PQ_TemporaryBuffs = {
	{spellID = PQ_JadeSpirit, check = true, hasBuff = false, endTime = nil},
	{spellID = PQ_Lightweave, check = true, hasBuff = false, endTime = nil},
	{spellID = PQ_JadeSerpent, check = true, hasBuff = false, endTime = nil},
	{spellID = PQ_PowerTorrent, check = true, hasBuff = false, endTime = nil},
	{spellID = PQ_VolcanicPotion, check = true, hasBuff = false, endTime = nil},
	{spellID = PQ_SynapseSprings, check = true, hasBuff = false, endTime = nil}
}

PQ_CheckTempBuffs = nil
function PQ_CheckTempBuffs(t)
	for i=1,#t do
		if t[i].check == true and UnitBuffID("player",t[i].spellID) then
			t[i].hasBuff = true
			t[i].endTime = select(7,UnitBuffID("player",t[i].spellID))
		else
			t[i].hasBuff = false
			t[i].endTime = nil
		end
	end
end

PQ_GetTimeLeft = nil
function PQ_GetTimeLeft(t, spellID)
	for i=1,#t do
		if t[i].spellID == spellID and t[i].hasBuff == true then
			return t[i].endTime - GetTime()
		end
	end
end

PQ_Round = nil
function PQ_Round(number, decimal)
	local multiplier = 10^(decimal or 0)
	return math.floor(number * multiplier + 0.5) / multiplier
end
-------------------------------------------------------------------------------
-- Mage Combustion Library
-------------------------------------------------------------------------------
function MCFrame_OnEvent(self,event,...)
	if event == "COMBAT_LOG_EVENT_UNFILTERED" then
		local subEvent		= select(2, ...)
		local source		= select(5, ...)
		local destination	= select(9, ...)
		local spell			= select(13, ...)
		local damage		= select(15, ...)
		local critical		= select(21, ...)
		local buffList = buffList
		
		if subEvent == "SPELL_PERIODIC_DAMAGE" then
			if UnitName("player") == source and destination == UnitName("target") then
				if spell == GetSpellInfo(12654) then  
					IgniteDamage = damage 
				end
			end
		end
		-- Aura removed events
		if subEvent == "SPELL_AURA_REMOVED" then
			if UnitName("player") == source then
				-- Ignite Removed
				if spell == GetSpellInfo(12654) then  
					IgniteDamage = 0 
				end
				-- Living Bomb fell off a target
				if spell == GetSpellInfo(44457) then
					LivingBomb = LivingBomb - 1
				end
				-- A proc or temporary buff removed.
				for i=1,#buffList do
					if spell == GetSpellInfo(buffList[i]) then
						Trinket = Trinket - 1
					end
				end
			end
		end
		-- Aura applied events
		if subEvent == "SPELL_AURA_APPLIED" then
			if UnitName("player") == source then
				-- Living Bomb applied to target.
				if spell == GetSpellInfo(44457) then
					LivingBomb = LivingBomb + 1
				end
				-- A proc or temporary buff applied.
				for i=1,#buffList do
					if spell == GetSpellInfo(buffList[i]) then
						Trinket = Trinket + 1
					end
				end
			end
		end
		-- Damage events
		if subEvent == "SPELL_DAMAGE" then
			if UnitName("player") == source and destination == UnitName("target") then
				if spell == GetSpellInfo(11366) then  
					PyroDamage = damage
					if critical == 1 then PyroCrit = 1 else PyroCrit = 0 end
				end
			end
		end
	end
end

--Racial Ids
PQ_RacialIDs = {
		28730,	--Arcane Torrent: Pally, Priest, Mage, Lock
		50613,	--Arcane Torrent: Death Knight
		80483,	--Arcane Torrent: Hunter
		129597,	--Arcane Torrent: Monk
		25046,	--Arcane Torrent: Rogue
		69179,	--Arcane Torrent: Warrior
		26297,	--Berserking: All Classes
		33702,	--Blood Fury: Mage, Lock
		33697,	--Blood Fury: Shaman, Monk
		20572,	--Blood Fury: Warrior, Hunter, Rogue, Death Knight
		7744,	--Will of the Forsaken: All Classes
		69041,	--Rocket Barrage: All Classes
		20594,	--StoneForm: All Classes
		20589,	--Escape Artist:All Classes
		59752	--Every Man for Himself
	}
	
Nova_Racial = nil
function Nova_Racial()
	local PQ_ActiveID = 0
		
	for i=1, #PQ_RacialIDs do
		if IsPlayerSpell(PQ_RacialIDs[i]) == true then
			PQ_ActiveID = PQ_RacialIDs[i]
		end
	end
	
	if PQ_ActiveID == 28730 then	--Arcane Torrent: Pally, Priest, Mage, Lock
		if GetSpellCooldown(PQ_ActiveID) == 0 
			and select(3, Nova_UnitInfo("player")) <= 98
			and UnitAffectingCombat("player")
			and SpecialUnit()
		then
			CastSpellByID(PQ_ActiveID)
			return true
		end
	elseif PQ_ActiveID == 50613 --Arcane Torrent: Death Knight
			or PQ_ActiveID == 80483 --Arcane Torrent: Hunter
			or PQ_ActiveID == 25046 --Arcane Torrent: Rogue
			or PQ_ActiveID == 69179 --Arcane Torrent: Warrior
		then
			if GetSpellCooldown(PQ_ActiveID) == 0 
				and select(4, Nova_UnitInfo("player")) <= 85
				and UnitAffectingCombat("player")
				and SpecialUnit()
			then
				CastSpellByID(PQ_ActiveID)
				return true
			end
	elseif PQ_ActiveID == 129597 then	--Arcane Torrent: Monk
		if GetSpellCooldown(PQ_ActiveID) == 0 
			and select(5, Nova_UnitInfo("player")) <= 3
			and UnitAffectingCombat("player")
			and SpecialUnit()
		then
			CastSpellByID(PQ_ActiveID)
			return true
		end
	elseif PQ_ActiveID == 26297 then	--Berserking: All Classes
		if GetSpellCooldown(PQ_ActiveID) == 0 
			and UnitAffectingCombat("player")
			and SpecialUnit()
		then
			CastSpellByID(PQ_ActiveID)
			return true
		end
	elseif PQ_ActiveID == 33702 --Blood Fury: Mage, Lock
			or PQ_ActiveID == 33697 --Blood Fury: Shaman, Monk
			or PQ_ActiveID == 20572 --Blood Fury: Warrior, Hunter, Rogue, Death Knight
		then	
			if GetSpellCooldown(PQ_ActiveID) == 0 
				and UnitAffectingCombat("player")
				and SpecialUnit()
			then
				CastSpellByID(PQ_ActiveID)
				return true
			end
	elseif PQ_ActiveID == 7744 then		--Will of the Forsaken: All Classes
		return false
	elseif PQ_ActiveID == 69041 then	--Rocket Barrage: All Classes
		return false
	elseif PQ_ActiveID == 20594 then	--StoneForm: All Classes
		return false
	elseif PQ_ActiveID == 20589 then	--Escape Artist:All Classes
		return false
	elseif PQ_ActiveID == 59752 then	--Every Man for Himself
		return false
	else
		return false
	end
end

-----------------------------------
------------- Sheuron -------------
-----------------------------------

function CheckAura(UnitID,SpellID,Filter,TimeLeft) 
  if not TimeLeft then TimeLeft = 0 end
  if type(SpellID) == "number" then SpellID = { SpellID } end 
  for i=1,#SpellID do 
    local spell, rank = GetSpellInfo(SpellID[i])
    if spell then
      local buff = select(7,UnitAura(UnitID,spell,rank,Filter)) 
      if buff and ( buff == 0 or buff - GetTime() > TimeLeft ) then return true end
    end
  end
end

function ImmuneTarget(t) 
  local buff = { 642, 45438, 31224, 23920, 33786, 19263, 97417, 97977, 102915, 100686, 105784, 74938, 
  				 106062, 113309, 117665 } 
  for i=1, #buff do if UnitBuffID(t,buff[i]) then return true end end
end

function BadEffects(t)
  local buff  = { 96328, 96325, 96326, 86788, 30108, 101810 } 
  for i=1, #buff do if UnitDebuffID(t,buff[i]) then return true end end
end

function AboutToDie(t) 
  local pressure = 0
  for i=1,#members do
    if UnitGroupRolesAssigned(members[i].Unit) ~= "HEALER" and UnitIsUnit(t,members[i].Unit..t) 
    then pressure = pressure + 1 end
  end
  if UnitHealth(t) < UnitHealthMax("player")*pressure and UnitHealthMax(t) ~= 1 
  then return true end
end

function CalculateHP(t)
  incomingheals = UnitGetIncomingHeals(t) or 0
  return 100 * ( UnitHealth(t) + incomingheals ) / UnitHealthMax(t)
end

function CanHeal(t)
  if UnitInRange(t) and UnitCanCooperate("player",t) and not UnitIsEnemy("player",t) 
  and not UnitIsCharmed(t) and not UnitIsDeadOrGhost(t) and not PQR_IsOutOfSight(t) 
  then return true end 
end

function GroupInfo()
  members, group = { { Unit = "player", HP = CalculateHP("player") } }, { low = 0, tanks = { } } 
  group.type = IsInRaid() and "raid" or "party" 
  group.number = GetNumGroupMembers()
  for i=1,group.number do if CanHeal(group.type..i) then 
    local unit, hp = group.type..i, CalculateHP(group.type..i) 
    table.insert( members,{ Unit = unit, HP = hp } ) 
    if hp < 90 then group.low = group.low + 1 end 
    if UnitGroupRolesAssigned(unit) == "TANK" then table.insert(group.tanks,unit) end 
  end end 
  if group.type == "raid" and #members > 1 then table.remove(members,1) end 
  table.sort(members, function(x,y) return x.HP < y.HP end)
  local customtarget = CanHeal("target") and "target" or CanHeal("mouseover") and GetMouseFocus() ~= WorldFrame and "mouseover" 
  if customtarget then table.sort(members, function(x) return UnitIsUnit(customtarget,x.Unit) end) end 
end

function ModSwitch(key,var,op1,op2)
	if key 
	  and not GetCurrentKeyBoardFocus() 
	  and ( not _G[var.."k"] or GetTime() - _G[var.."k"] > 0.3 ) then
    	_G[var.."k"] = GetTime()
    	if _G[var] then
    		_G[var] = false 
    		xrn:message(op1) 
    	else 
    		_G[var] = true 
    		xrn:message(op2) 
    	end
  	end
end


function AssistTank() 
  local tank = group.tanks[1] 
  if tank and group.type == "party" 
  and not UnitExists("target") 
  and UnitAffectingCombat(tank) 
  and UnitAffectingCombat(tank.."target") 
  and UnitCanAttack("player",tank.."target")
  then TargetUnit(tank.."target") end
end

local function onUpdate(self,elapsed) 
  if self.time < GetTime() - 2.8 then
    if self:GetAlpha() == 0 then self:Hide() else self:SetAlpha(self:GetAlpha() - .05) end
  end
end

xrn = CreateFrame("Frame",nil,ChatFrame1) 
xrn:SetSize(ChatFrame1:GetWidth(),30)
xrn:Hide()
xrn:SetScript("OnUpdate",onUpdate)
xrn:SetPoint("TOP",0,0)
xrn.text = xrn:CreateFontString(nil,"OVERLAY","MovieSubtitleFont")
xrn.text:SetAllPoints()
xrn.texture = xrn:CreateTexture()
xrn.texture:SetAllPoints()
xrn.texture:SetTexture(0,0,0,.50) 
xrn.time = 0

function xrn:message(message) 
  self.text:SetText(message)
  self:SetAlpha(1)
  self.time = GetTime() 
  self:Show() 
end